﻿using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks;

namespace pdfer.Renders
{
    internal class GraphicsState
    {
        #region Device-independent graphics state parameters
        /// <summary>
        /// 当前转换矩阵，它将位置从用户坐标映射到设备坐标（请参阅第 4.2 节 “坐标系统参数”）。
        /// <para>
        /// 该矩阵由坐标变换运算符 cm 的每个应用程序修改。初始值：将默认用户坐标转换为设备坐标的矩阵。
        /// </para>
        /// </summary>
        public Double[] CTM {  get; set; }

        /// <summary>
        /// 当前剪切路径，它定义了所有输出要裁剪的边界（参见第 4.4.3 节 “剪切路径运算符”）。
        /// <para>
        /// 初始值：输出页面的整个可成像部分的边界。
        /// </para>
        /// </summary>
        public Int32[] ClippingPath {  get; set; }

        /// <summary>
        /// 要在其中解释颜色值的当前色彩空间（请参阅第 4.5 节 “色彩空间”）。
        /// <para>
        /// 有两个单独的色彩空间参数：一个用于描边，另一个用于所有其他绘画作。初始值：DeviceGray。
        /// </para>
        /// </summary>
        public ColorSpace ColorSpace { get; set; } = ColorSpace.DeviceGray;

        /// <summary>
        /// 在绘画作期间要使用的当前颜色（请参阅 第 4.5 节 “色彩空间”）。
        /// <para>
        /// 此参数的类型和解释取决于当前色彩空间;对于大多数色彩空间，
        /// 颜色值由 1 到 4 个数字组成。有两个单独的颜色参数：一个用于描边，另一个用于所有其他绘画作。初始值：黑色。
        /// </para>
        /// </summary>
        public Int32[] Color {  get; set; }

        /// <summary>
        /// 一组 9 个图形状态参数，这些参数仅与文本绘画有关。
        /// <para>
        /// 这些参数包括用于选择字体、将字形缩放到适当大小以及实现其他效果的参数。文本状态参数在第 5.2 节 “文本状态参数和运算符”中介绍。
        /// </para>
        /// </summary>
        public TextStateParam TextState { get; set; } = new TextStateParam();

        /// <summary>
        /// 要描边的路径的粗细，以用户空间单位表示（请参阅第 215 页的“线宽”）。
        /// <para>
        /// 初始值：1.0。
        /// </para>
        /// </summary>
        public Double LineWidth { get; set; } = 1.0;

        /// <summary>
        /// 指定任何描边开放路径的端点形状的代码（请参阅第 216 页的“Line Cap Style”）。
        /// <para>
        /// 初始值：0，对于方形平底端头。
        /// 0 Butt cap.  1 Round cap. 2 Projecting square cap. 
        /// </para>
        /// </summary>
        public Int32 LineCap { get; set; }
        /// <summary>
        /// 指定描边路径的连接段之间关节形状的代码（请参阅第 216 页的“Line Join Style”）。
        /// <para>
        /// 初始值：0，用于斜接联接。
        /// </para>
        /// 0 Miter join. 1 Round join 2 Bevel join
        /// </summary>
        public Int32 LineJoin { get; set; }

        /// <summary>
        /// 描边路径的斜接线连接的最大长度（请参阅第 217 页上的“斜接限制”）。
        /// <para>
        /// 此参数限制了线段以锐角连接时产生的“尖峰”的长度。初始值：10.0，对于低于大约 11.5 度的斜接截止。
        /// </para>
        /// </summary>
        public Double MiterLimit { get; set; } = 10.0;

        /// <summary>
        /// 对路径进行描边时使用的虚线图案的说明（请参阅第 217 页上的“线条虚线图案”）。
        /// <para>
        /// 初始值：实线。a solid line
        /// </para>
        /// 这里特殊处理 数组的第一个数字代表类型 后面的代表相位
        /// [0] 实线、不间断的线条
        /// [0, 3] |3 units on, 3 units off, …
        /// [1, 2] |1 on, 2 off, 2 on, 2 off, …
        /// [0, 2, 1] 2 on, 1 off, 2 on, 1 off, …
        /// [6, 3, 5] 2 off, 3 on, 5 off, 3 on, 5 off, …
        /// [11, 2, 3] 1 on, 3 off, 2 on, 3 off, 2 on, …
        /// </summary>

        public Int32[] DashPattern { get; set; } = [0];

        /// <summary>
        /// 将基于 CIE 的颜色转换为设备颜色时要使用的渲染方法（请参阅第 260 页上的“渲染方法”）。
        /// <para>
        /// 初始值：RelativeColorimetric。
        /// </para>
        /// </summary>
        public String RenderingIntent { get; set; } = "/RelativeColorimetric";

        /// <summary>
        /// （PDF 1.2）一个标志，用于指定在对线宽相对于输出设备的像素分辨率较小的路径进行描边时，是否补偿可能的渐变效果（请参阅第 6.5.4 节 “自动描边调整”）。
        /// <para>
        /// 请注意，这是一个与设备无关的参数，即使其效果的细节取决于设备。初始值：false。
        /// </para>
        /// </summary>
        public Boolean StrokeAdjustment { get; set; }

        /// <summary>
        /// （PDF 1.4）要在透明成像模型中使用的当前混合模式（请参阅第 7.2.4 节 “混合模式” 和 7.5.2 “指定混合色彩空间和混合模式”）。
        /// <para>
        /// 此参数在透明度组 XObject 开始执行时隐式重置为其初始值（请参阅第 7.5.5 节 “透明度组 XObjects”）。初始值：正常。
        /// </para>
        /// </summary>
        public String[] BlendMode { get; set; } = ["Normal"];

        /// <summary>
        /// （PDF 1.4）软蒙版字典（请参阅第 552 页的“软蒙版词典”），
        /// <para>
        /// 指定要在透明成像模型中使用的蒙版形状或蒙版不透明度值（请参阅第 526 页的“源形状和不透明度”和第 550 页的“蒙版形状和不透明度”），
        /// </para>
        /// <para>
        /// 如果未指定此类蒙版，则为名称 None。
        /// </para>
        /// 此参数在透明度组 XObject 开始执行时隐式重置为其初始值（请参阅第 7.5.5 节 “透明度组 XObjects”）。初始值：None。
        /// </summary>
        public Dictionary<String, Object>? SoftMask { get; set; }

        /// <summary>
        /// （PDF 1.4）要在透明成像模型中使用的恒定形状或恒定不透明度值（请参阅第 526 页上的“源形状和不透明度”和第 551 页上的“恒定形状和不透明度”）。
        /// <para>
        /// 有两个单独的 Alpha 常量参数：一个用于描边，另一个用于所有其他绘制作。
        /// </para>
        /// <para>
        /// 此参数在透明度组 XObject 开始执行时隐式重置为其初始值（请参阅 第 7.5.5 节 “透明组 XObjects”）。初始值：1.0。
        /// </para>
        /// </summary>
        public Double AlphaConstant { get; set; } = 1.0;

        /// <summary>
        /// （PDF 1.4）一个标志，用于指定是将当前软蒙版和 alpha 常数参数解释为形状值 （true） 还是不透明度值 （false）。
        /// 此标志还控制图像字典中 SMask 条目（如果有）的解释（参见第 4.8.4 节 “图像字典”）。初始值：false。
        /// </summary>
        public Boolean AlphaSource { get; set; }

        #endregion

        #region Device-dependent graphics state parameters

        /// <summary>
        /// （PDF 1.2）一个标志，指定（在支持叠印控制功能的输出设备上）在一组着色剂中绘画是否应导致其他着色剂的相应区域被擦除 （false） 或保持不变 （true）;
        /// <para>
        /// 参见第 4.5.6 节 “叠印控制”。在 PDF 1.3 中，有两个单独的叠印参数：一个用于描边，另一个用于所有其他绘画作。初始值：false。
        /// </para>
        /// </summary>
        public Boolean Overprint { get; set; }

        /// <summary>
        /// （PDF 1.3）一个代码，用于指定在叠印时，
        /// DeviceCMYK 色彩空间中的颜色组件值 0 是应擦除该组件 （0） 还是保持不变 （1）（请参阅第 4.5.6 节 “叠印控制”）。初始值：0。
        /// </summary>
        public Double OverprintMode { get; set; }

        /// <summary>
        /// （PDF 1.2）一个函数，用于计算将 RGB 颜色转换为 CMYK 时要使用的黑色分量的级别（请参阅第 6.2.3 节 “从 DeviceRGB 到 DeviceCMYK 的转换”）。
        /// 初始值：取决于安装。
        /// </summary>
        public Action BlackGeneration { get; set; }
        /// <summary>
        /// （PDF 1.2）一个函数，用于计算青色、洋红色和黄色分量色阶的减少，以补偿黑色生成所添加的黑色量（请参阅第 6.2.3 节 “从 DeviceRGB 到 DeviceCMYK 的转换”）。初始值：取决于安装。
        /// </summary>
        public Action UndercolorRemoval { get; set; }

        /// <summary>
        /// （PDF 1.2）调整装置灰度或颜色分量电平以补偿特定输出装置中的非线性响应的函数（参见第 6.3 节 “传递函数”）。初始值：取决于安装。
        /// </summary>
        public Action Transfer { get; set; }

        /// <summary>
        /// (PDF 1.2） 用于灰度和颜色渲染的半调网屏，指定为半调词典或流（参见第 6.4 节 “半调”）。初始值：取决于安装。
        /// </summary>
        public Object Halfone {  get; set; }

        /// <summary>
        /// 在输出设备上渲染曲线的精度（请参阅 第 6.5.1 节 “平坦度容差”）。
        /// <para>
        /// 此参数的值提供最大误差容限，以输出设备像素为单位;较小的数字提供更平滑的曲线，但代价是更多的计算和内存使用。初始值：1.0。
        /// </para>
        /// </summary>
        public Double Flatness { get; set; } = 1.0;

        /// <summary>
        /// （PDF 1.3）在输出设备上任颜色渐变的精度（请参阅第 6.5.2 节 “平滑度容忍度”）。
        /// <para>
        /// 此参数的值给出了最大容错能力，表示为每个颜色成分范围的分数;较小的数字提供更平滑的颜色过渡，但代价是消耗更多的计算和内存。初始值：取决于安装。
        /// </para>
        /// </summary>
        public Double Smoothness { get; set; } 
        #endregion

    }

    internal enum ColorSpace
    {
        DeviceGray
    }

    internal class TextStateParam
    {
        /// <summary>
        /// 字符间距
        /// </summary>
        public Double Tc { get; set; } = 0;
        /// <summary>
        /// 字间距
        /// </summary>
        public Double Tw { get; set; } = 0;
        /// <summary>
        /// 水平缩放
        /// </summary>
        public Double Th { get; set; } = 100;
        /// <summary>
        /// 
        /// </summary>
        public Double Tl { get; set; } = 0;
        /// <summary>
        /// 字体
        /// </summary>
        public String Tf { get; set; }
        /// <summary>
        /// 字体大小
        /// </summary>
        public Double Tfs { get; set; }
        /// <summary>
        /// 呈现模式 0 填充 1 描边 2 描边+填充
        /// </summary>
        public Int32 Tmode { get; set; } = 0;
        /// <summary>
        /// 文本上升
        /// </summary>
        public Double Trise { get; set; } = 0;
        /// <summary>
        /// 文本挖空
        /// </summary>
        public Double Tk { get; set; }
    }
}
